package cn.practice.chat.config;

import cn.practice.chat.handler.WebSocketChannelHandler;
import com.alibaba.nacos.api.naming.NamingFactory;
import com.alibaba.nacos.api.naming.NamingService;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelOption;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import lombok.extern.slf4j.Slf4j;

import java.net.InetAddress;


/**
 * @ClassName WebSocket
 * @Description:
 * @Author A-TAO
 * @Date 2022/10/30
 * @Version V1.0
 **/
@Slf4j
public class WebSocket {

    /**
     * @description 启动netty 并且注册到nacos中 ，用来做集群
     * @param nettyName netty服务
     * @param port 端口
     **/
    public static void action(String nettyName, Integer port, String nacosUrl){
        EventLoopGroup bossGroup = new NioEventLoopGroup();
        EventLoopGroup workGroup = new NioEventLoopGroup();
        try {
            ServerBootstrap serverBootstrap = new ServerBootstrap();
            serverBootstrap.group(bossGroup, workGroup);
            // 设置服务端通道实现类
            serverBootstrap.channel(NioServerSocketChannel.class);
            // 设置线程队列得到连接个数
            serverBootstrap.option(ChannelOption.SO_BACKLOG, 128);
            ////设置保持活动连接状态
            serverBootstrap.childOption(ChannelOption.SO_KEEPALIVE, true);
            serverBootstrap.childHandler(new WebSocketChannelHandler());
            // 绑定端口，启动服务
            ChannelFuture channelFuture = serverBootstrap.bind(port).sync();
            log.info(WebSocket.class + "已启动，正在监听： " + channelFuture.channel().localAddress());
            //获取nacos服务
            NamingService namingService = NamingFactory.createNamingService(nacosUrl);
            //将服务注册到注册中心
            InetAddress address = InetAddress.getLocalHost();
            namingService.registerInstance(nettyName, address.getHostAddress(), port);
            log.info("注册到nacos成功，nettyName={}，port={}", nettyName, port);

            //对关闭通道进行监听
            channelFuture.channel().closeFuture().sync();
        }catch (Exception e){
            e.printStackTrace();
        }finally {
            //退出程序
            bossGroup.shutdownGracefully();
            workGroup.shutdownGracefully();
        }

    }

}
